package com.nstar.base.util
{
	import flash.display.BitmapData;
	import flash.display.DisplayObject;
	import flash.display.GradientType;
	import flash.display.Graphics;
	import flash.display.SpreadMethod;
	import flash.display.Sprite;
	import flash.filters.BitmapFilterQuality;
	import flash.filters.BlurFilter;
	import flash.geom.Matrix;
	import flash.geom.Point;
	
	import mx.containers.Canvas;
	import mx.core.Container;
	import mx.utils.ColorUtil;
	
	public class GraphicsUtils
	{
		//layout
		public static const LAYOUT_TILE:String = "tile";
		public static const LAYOUT_CENTER:String = "center";
		public static const LAYOUT_STRETCH:String = "stretch";
				
		public function GraphicsUtils()
		{
		}
		/**
		 * drawSector: 画任意角度的扇形
		 * g		:要在上面绘制的对象.
		 * x,y		:扇形的中心点，即圆心
		 * r		:扇形半径
		 * angle	:扇形的角度
		 * startFrom:扇形角度的起始位置，顺时针方向算起，270 上, 180 左, 0 右, 90 下 
		 * color	:填充颜色
		 */
		public static function drawSector(g:Graphics,bgcolor:uint=0xCCCCCC,borderColor:uint=0xCCCCCC,
			x:Number=200,y:Number=200,r:Number=100,
			angle:Number=27,startFrom:Number=270):void {
		    
		    g.beginFill(borderColor);
		    //remove this line to unfill the sector
		    /* the border of the secetor with color 0xff0000 (red) , you could replace it with any color 
		    * you want like 0x00ff00(green) or 0x0000ff (blue).
		    */
		    g.lineStyle(0,0xff0000,0);
		    g.moveTo(x,y);
		    angle=(Math.abs(angle)>360)?360:angle;
		    var n:Number=Math.ceil(Math.abs(angle)/45);
		    var angleA:Number=angle/n;
		    angleA=angleA*Math.PI/180;
		    startFrom=startFrom*Math.PI/180;
		    g.lineTo(x+r*Math.cos(startFrom),y+r*Math.sin(startFrom));
		    for (var i=1; i<=n; i++) {
		        startFrom+=angleA;
		        var angleMid=startFrom-angleA/2;
		        var bx=x+r/Math.cos(angleA/2)*Math.cos(angleMid);
		        var by=y+r/Math.cos(angleA/2)*Math.sin(angleMid);
		        var cx=x+r*Math.cos(startFrom);
		        var cy=y+r*Math.sin(startFrom);
		        g.curveTo(bx,by,cx,cy);
		    }
		    if (angle!=360) {
		        g.lineTo(x,y);
		    }
		    g.endFill();// if you want a sector without filling color , please remove this line.
		}
		
		//绘制指定数量的色轮
		//sourceColors:原色
		//count:要绘制的色轮数
		public static function drawColorWheel(g:Graphics,centerX:Number,centerY:Number,radius:Number,
			sourceColors:Array,count:int):void{
			sourceColors = generateColors(sourceColors,count);
			for(var i:int =0;i<sourceColors.length;i++){
				GraphicsUtils.drawSector(g,centerX,centerY,radius,360/count,270+i*30,sourceColors[i]);
			}  
			g.beginFill(0xFFFFFF);
			g.drawCircle(centerX,centerY,50);
			g.endFill();
		}
		
		//根据源颜色数据生成相应数量的色相环所需要的颜色
		private static function generateColors(sourceColors:Array,count:int):Array{
			var colors:Array = new Array();
			//复制源颜色
			for each(var item:uint in sourceColors){
				colors.push(item);
			}
			
			var nextIdx:int = 0;
			for(var i:int=0;i<sourceColors.length;i++){
				nextIdx = i+1;
				if(nextIdx==sourceColors.length)
					nextIdx = 0;
				
				var mixColor:uint = ColorUtils.mixColor(sourceColors[i],sourceColors[nextIdx]);
				colors.push(mixColor);
			}
			colors.sort();//颜色排序
			if(colors.length!=count){
				colors = generateColors(colors,count);
			}
			return colors;
		}
		
		/**
		 * 方法说明 : 画彩色进度条
		 * 参数说明 :
		 * 		g : 要在其上画进度条的对象 
		 * 		bytesLoaded : 已经加载的字节值
		 * 		bytesTotal  : 总共的字节值
		 * 		x			: 进度条的x坐标
		 * 		y			: 进度条的y坐标
		 * 		barWidth	: 进度条的总宽度
		 * 		barHeight	: 进度条的高度
		 * 		colors		: 颜色数组
		 */ 
		public static function drawColorProgressBar(g:Graphics,bytesLoaded:Number,bytesTotal:Number,
			x:Number = 0,y:Number = 0,barWidth:Number=300,barHeight:Number=20,colors:Array=null):void 
		{   
			//颜色块间隔
			var gap:Number = 5;
			//开始位置的偏移值
			g.clear(); 
			g.lineStyle(2,0xFFFFFF,0.5);
			//如果没有提供颜色值，则设置默认的颜色值
			if(!colors){
				colors = [
					0xA6CE39,0x23B14B,0x01AAAD,0x0173BC,0x015AAC,0x5B2D90,
					0xA4228E,0xEE183A,0xF47322,0xF8941D,0xFDB815,0xFFD403
				];				
			}
			//先画背景色
			var w:Number = (barWidth-(colors.length-1)*gap)/colors.length;
			for(var i:int=0;i<colors.length;i++){
				g.beginFill(colors[i]);
				var px:Number = i*(w+gap);
				g.drawRoundRect(x+px,y,w,barHeight,5,5);
				g.endFill();					
			}
			
			g.lineStyle(2,0xFFFFFF,1);
			//算出进度百分比
			var per:Number = Math.floor(colors.length*(bytesLoaded/bytesTotal));
			//通过调亮原始颜色值来表示进度
			for(var i:int=0;i<per;i++){
				g.beginFill(ColorUtil.adjustBrightness(colors[i],80));
				var px:Number = i*w+i*gap;
				g.drawRoundRect(x+px,y,w,barHeight,5,5);
				g.endFill();	
			}
				
		}
		
		public static function drawStripeBackground(g:Graphics,colors:Array,w:Number,h:Number):void{
			g.clear();
			var step:Number = w/colors.length;
			for (var i:int =0;i<colors.length;i++){
				g.beginFill(uint(colors[i]));
				g.drawRect(i*step,0,step,h);
			}
			g.endFill();
		}
		
		public static function drawGradient(g:Graphics,colors:Array,w:Number,h:Number,
			angle:Number = 0,ratios:Array=null):void{
		  	var fillType:String = GradientType.LINEAR;
		  	var alphas:Array = new Array();
		  	
		  	if(angle == NaN) angle = 0;
		  	
		  	for (var i:int = 0 ;i<colors.length;i++){
		  		alphas.push(1);
		 	}
		  	if(ratios==null){
			  	ratios = new Array();
			  	var step:int = Math.round(255/colors.length);
			  	for (var i:int = 0 ;i<colors.length;i++){
			  		ratios.push(step*i);
			  	}
		  	}
		  
		  	g.clear();
		  	var matr:Matrix = new Matrix();
		  	matr.createGradientBox(w, h, Math.PI*angle/180, 0, 0);
		  	var spreadMethod:String = SpreadMethod.PAD;
		  	g.beginGradientFill(fillType, colors, alphas, ratios, matr, spreadMethod);  
		  	g.drawRect(0,0,w,h);				
		}		
		
		//AIR应用下载的进度条渐变色 [0x004176,0x087fb5]，可参考
		public static function drawGradientRect(g:Graphics,x:Number = 0,y:Number = 0,
			w:Number = 100,h:Number=10,color1:uint = 0x346bac,color2:uint = 0x34b5f9):void{
			var matrix:Matrix=new Matrix(); 
			matrix.createGradientBox(w,h,Math.PI/2,0,0); 
			var spreadMethod:String = SpreadMethod.PAD;
			var alphas:Array=[1,1]; 
			var ratios:Array=[0,255]; 
			var colors:Array = [color1,color2];
			g.beginGradientFill(GradientType.LINEAR,colors,alphas,ratios,matrix,spreadMethod);        
			g.drawRect(x,y,w,h); 
			g.endFill();  			
		}
		
	    //在Canvas中使用位图绘制背景,填充方式有平铺、居中、拉伸、默认背景透明色为白色
	    public static function drawBackground(source:DisplayObject,
	    	dest:Container,layout:String=LAYOUT_TILE):void{
	    	dest.graphics.clear();
	    	var cw:Number = source.width;
	    	var ch:Number = source.height;
	    	
	    	var bd:BitmapData = new BitmapData(cw,ch);
	    	bd.draw(source,new Matrix());
	    	var matrix:Matrix = new Matrix();//用于对目标位图进行的转换操作
	    	
	    	switch(layout){
	    		case LAYOUT_TILE:
	    			dest.graphics.beginBitmapFill(bd,matrix);
	    			dest.graphics.drawRect(0,0,dest.width,dest.height);
	    			break;
	    		case LAYOUT_CENTER:
			    	var p:Point = new Point();
			    	p.x = (dest.width-cw)/2;
			    	p.y = (dest.height - ch)/2;	  
			    	matrix.translate(p.x,p.y);  		
	    			dest.graphics.beginBitmapFill(bd,matrix);
	    			dest.graphics.drawRect(p.x,p.y,cw,ch);
	    			break;
	    		case LAYOUT_STRETCH:
	    			matrix.scale(dest.width/cw,dest.height/ch);
			    	dest.graphics.beginBitmapFill(bd,matrix,false);
			    	dest.graphics.drawRect(0,0,dest.width,dest.height);	    			
	    			break;
	    	}
	    	dest.graphics.endFill();
	    }
	    
	    public static function addBlur(item:Object,w:Number=280,h:Number=80):Sprite{
			
			var sprite:Sprite = new Sprite();
			item.rawChildren.addChild(sprite);
			sprite.x = (item.width-w)/2;
			sprite.y = (item.height-h)/2;
			sprite.graphics.beginFill(0xFFFFFF,0.45); 
			sprite.graphics.drawEllipse(sprite.width/2, sprite.height/2, w, h); 
			sprite.graphics.endFill(); 
			
			var blur:BlurFilter = new BlurFilter(); 
			blur.blurX = 150; 
			blur.blurY = 50; 
			blur.quality = BitmapFilterQuality.HIGH; 
			sprite.filters = [blur];
			return sprite;
	    }
	    
	    //在容器上画仿PS透明背景格子
	    public static function drawTransparencyBackground(container:Container,
	    	color1:uint = 0xFFFFFF,color2:uint = 0xF0F0F0):void{
	    	var W:Number = 8;
	    	var H:Number = 8;
	    	var w1:Number = container.width;
	    	var h1:Number = container.height;
	    	var cols:int = Math.floor(w1/(2*W));
	    	var rows:int = Math.floor(h1/(2*H));
	    	
	    	var m:Canvas = new Canvas();
	    	m.visible = m.includeInLayout = false;
	    	m.x = m.y = 0;
	    	m.graphics.clear();
	    	m.graphics.beginFill(0xFFFFFF);
	    	m.graphics.drawRect(0,0,w1-1,h1-1);
	    	
	    	
	    	var g:Graphics = container.graphics;
	    	g.clear();
	    	for(var i:int = 0;i<rows+1;i++){
	    		for(var j:int = 0;j<cols+1;j++){
	    			g.beginFill(color1);
	    			g.drawRect(j*W*2,2*i*H,W,H);
	    			
	    			g.beginFill(color2);
	    			g.drawRect(j*W*2+W,2*i*H+H,W,H);
	    		}
	    	}
	    	
	    	container.addChild(m);
	    	container.mask = m;
	    }
	    
	    public static function drawZebraStripe(container:Container,color1:uint,color2:uint,size:Number,direction:String="v"):void{
	    	var g:Graphics = container.graphics;
	    	g.clear();
	    	
	    	var w1:Number = container.width;
	    	var h1:Number = container.height;
	    	
	    	switch(direction){
	    		case "h":
			    	var n1:int = int(h1/size)+1;
			    	for (var i:int = 0;i<n1;i++){
			    		if(i%2==0){
			    			g.beginFill(color1);
			    		}else{
			    			g.beginFill(color2);
			    		}
			    		if(i*size+size>container.height){
			    			g.drawRect(0,i*size,w1,container.height-i*size);
			    		}else{
			    			g.drawRect(0,i*size,w1,size);
			    		}
			    	}	 	    		
	    			break;
	    		case "v":
			    	var n1:int = int(w1/size)+1;
			    	for (var i:int = 0;i<n1;i++){
			    		if(i%2==0){
			    			g.beginFill(color1);
			    		}else{
			    			g.beginFill(color2);
			    		}
			    		if(i*size+size>container.width){
			    			g.drawRect(i*size,0,container.width-i*size,h1);
			    		}else{
			    			g.drawRect(i*size,0,size,h1);
			    		}
			    	}	    	
	    			break;
	    	}
	    	
	    }
	    
	    //画表格
	    public static function drawGrid(container:Container,gridSize:Number=10,color:uint=0xF2F2F2,alpha:Number=0.1):void{
	    	var w1:Number = container.width;
	    	var h1:Number = container.height;
	    	var n1:int = Math.round(w1/gridSize);
	    	var n2:int = Math.round(h1/gridSize);
	    	var g:Graphics = container.graphics;
	    	g.clear();
	    	g.lineStyle(1,color,alpha);
	    	//先从左到右
	    	for(var i:int = 0;i<n1;i++){
	    		g.moveTo(i*gridSize,0);
	    		g.lineTo(i*gridSize,h1);
	    	}
	    	//再从上到下
	    	for(var i:int = 0;i<n2;i++){
	    		g.moveTo(0,i*gridSize);
	    		g.lineTo(w1,i*gridSize);
	    	}
	    }
	    
		public static function randomPolygon4(x1:Number,x2:Number,
			minHeight:Number,maxHeight:Number,y2:Number):Array{
			var ry1:Number = SystemUtils.randRange(minHeight,maxHeight);
			var ry2:Number = SystemUtils.randRange(minHeight,maxHeight);
			var p1:Point = new Point(x1,ry1);
			var p2:Point = new Point(x2,ry2);
			var p3:Point = new Point(x2,y2);
			var p4:Point = new Point(x1,y2);
			
			
			var result:Array = new Array();
			result.push(p1);
			result.push(p2);
			result.push(p3);
			result.push(p4);
			
			return result;
		} 
		
		//创建小山型的区域
		public static function randomHillShape():Array{
			var result:Array = new Array();
			
			return result;
		}
		
		public static function drawPolygon(container:Container,lineColor:uint,fillColor:uint,
			points:Array):void{
			var g:Graphics = container.graphics;
			g.clear();
			g.lineStyle(1,lineColor);
			g.beginFill(fillColor);
			g.moveTo(points[0].x,points[0].y);
			for(var i:int = 0;i<points.length;i++){
				var x1:Number = points[i].x;
				var y1:Number = points[i].y;
				
				var x2:Number;
				var y2:Number;
				if(i==points.length-1){
					x2 = points[0].x;
					y2 = points[0].y;
				}else{
					x2 = points[i+1].x;
					y2 = points[i+1].y;						
				}
				
				g.lineTo(x2,y2);
			}
			g.endFill();
		}	    
		
		
	}
}